/**
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.

 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.

 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 */
package org.jimm.protocols.icq.core;

import java.io.DataInputStream;
import java.io.IOException;
import java.util.concurrent.BlockingQueue;

import android.util.Log;
import org.jimm.protocols.icq.core.exceptions.LoginException;
import org.jimm.protocols.icq.exceptions.BadPacketException;
import org.jimm.protocols.icq.integration.events.LoginErrorEvent;
import org.jimm.protocols.icq.integration.listeners.OurStatusListener;

/**
 * <p>
 * Created by 13.06.2008
 * 
 * @author Samolisov Pavel
 * @author Prolubnikov Dmitry
 */
public class OscarPacketHandler implements Runnable {

	private static final String LOG_TAG = "ICQ:OscarPacketHandler";

	public static final String THREAD_NAME = "OscarPacketHandlerThread";

	private final Thread thread = new Thread(this);
	private OscarPacketAnalyser mAnalyser;
	private BlockingQueue<DataInputStream> mMessageQueue;

	private volatile boolean runnable = true;

	public OscarPacketHandler(OscarPacketAnalyser analyser,
			BlockingQueue<DataInputStream> messageQueue) {
		mAnalyser = analyser;
		mMessageQueue = messageQueue;
		thread.start();
	}

	public void run() {
		try {
			while (runnable) {
				try {
					mAnalyser.handlePacket(mMessageQueue.take());
				} catch (BadPacketException e) {
					Log.e(LOG_TAG, "Bad packet", e);
				} catch (IOException e) {
					Log.e(LOG_TAG, "Error handling packet", e);
				}
			}
		} catch (InterruptedException ex) {
			Log.d(LOG_TAG, "Oscar packet analysing interrupted");
		} catch (LoginException ex) {
			// create event and notifycation
			try {
			LoginErrorEvent e = new LoginErrorEvent(ex.getErrorType());
			for (int i = 0; i < mAnalyser.getConnection()
					.getOurStatusListeners().size(); i++) {
				OurStatusListener l = (OurStatusListener) mAnalyser
						.getConnection().getOurStatusListeners().get(i);

				Log.d(LOG_TAG,
						"notify listener " + l.getClass().getName()
								+ " onAuthorizationFailed() '" + "because "
								+ e.getErrorMessage());

				l.onAuthorizationFailed(e);
			}
			} catch (NullPointerException e) {
				// сюда попадаем в случае, если в этот момент остановили Handler (вызвали stopHandler)
				Log.d(LOG_TAG, e.getLocalizedMessage());
			}
			runnable = false;
		}
	}

	public synchronized void stopHandler() {
		Log.d(LOG_TAG, "OscarPacketHandler thread has been stoped");
		runnable = false;
		thread.interrupt();
		mMessageQueue = null;
		mAnalyser = null;
	}
}
